
#include <e93196_config.h>

/*******************************************************************************
 * @brief SendBit
 *
 * @param bData [in] uint8_t, 0 or 1 to send
 *
 * @return none
*******************************************************************************/
static void SendBit(uint8_t bData)
{	
	e93196_hal_serin_pin_low();   //PIR_SERIN = 0;
	e93196_delay_us(5);	   // 1us -5 us
	e93196_hal_serin_pin_hight();  //PIR_SERIN = 1;
	e93196_delay_us(5);	   // 1us -5us
	if(bData)
	{
       e93196_hal_serin_pin_hight();  //PIR_SERIN = 1;
	}
	else
	{
	   e93196_hal_serin_pin_low();	  //PIR_SERIN = 0;
	}			
	e93196_delay_us(80);	  //100us -90us
}	

/*******************************************************************************
 * @brief SendValue to send the variable bits
 *
 * @param value [in] uint8_t, the value to sent,
 * @param bitcount [in] uint8_t, the value low bitcount to sent
 *
 * @return none
*******************************************************************************/
static void SendValue(uint8_t value, uint8_t bitcount)
{
 uint8_t valueTemp,i,maxi;
   valueTemp = value;
   if (bitcount > 8)
   	  maxi = 8;
   else
   	  maxi = bitcount;
   i = 8 - maxi;
   valueTemp = valueTemp << i;
   for (i = 0; i < maxi; i++) 
   {
	  if((valueTemp & 0x80) == 0x80) 
	  { 
		 SendBit(1);
	  } 
	  else 
	  { 
		 SendBit(0);
	  } 
	  valueTemp = valueTemp << 1; 
   }
}

/*******************************************************************************
 * @brief Sete93196 to set e93196 register
 *
 * @param sensitivity [in] uint8_t, the sensitivity to set
 * @param pulse_counter [in] uint8_t, the pulse_counter to set
 * @param motion_enable [in] uint8_t, the motion_enable to set
 *
 * @return none
*******************************************************************************/
void e93196_set(uint8_t sensitivity , uint8_t pulse_counter, uint8_t motion_enable)
{
   uint8_t temp_data;
   
  	e93196_hal_serin_pin_out_mod();
	
   // send start  serin pin chang 0 to 1 start
   e93196_hal_serin_pin_low();     //  PIR_SERIN = 0;
   e93196_delay_us(1000);		//1000us

   //first 8 bits sensitivity (value * 6.5uV)
   temp_data = sensitivity;  //default 0x0C
   SendValue(temp_data,8);
   
   //send Blind time 4 bits (0.5s * val)
   temp_data = 4; //default 9
   SendValue(temp_data,4);
   
   //send Pluse Counter 2 bits (value + 1)
   temp_data = pulse_counter;  //default 2pluse
   if (temp_data > 3) temp_data = 3;
   SendValue(temp_data,2);

   //send Window Time 2 bits (value +1)*4s
   temp_data = 0;  //default 4s
   SendValue(temp_data,2);

   //send Motion Detector Enable 1bit 1:enable
   temp_data = motion_enable;
   if (temp_data) temp_data = 1;
   SendValue(temp_data,1);
   
   //send Interrupt Source  1 bit 0:motion 1:filter
   SendBit(0);
   
   //send ADC/Filter Voltage 2 bits 
   temp_data = 1;  //default 0 PIR, BFP out
   SendValue(temp_data,2);

   //send Supply Regulator Enable 1bit 0 use 2.2V out
   SendBit(0);
   
   //start self-test 1bit when 0 to 1 change sart self test
   SendBit(0);
   
   //send sample capactitor size 1bit 
   SendBit(0);	
   
   //send User test-mode select 2bits
   temp_data = 0;  //default 0 reserve
   SendValue(temp_data,2);		
   
   // send end	
   e93196_hal_serin_pin_low();     //PIR_SERIN = 0;	
   
   e93196_hal_serin_pin_lowpower_mod();
   e93196_delay_us(1000);	       //1000us  
}

/*******************************************************************************
 * @brief Sete93196 Sensitivity level
 *
 * @param level [in] uint8_t, the level to set, total 4 level
 *
 * @return none
*******************************************************************************/
void e93196_set_default(void)
{
	e93196_set(0x10, 1 , 1); //default value 0x0c, 0x01, 0x01
}
/*******************************************************************************
 * @brief clear motion interrupt pin 
 *
 * @param none
 *
 * @return none
*******************************************************************************/
void e93196_Clear_Interrupt_Pin(void)
{
	e93196_hal_int_pin_disable_int_mod();
	e93196_hal_int_pin_out_mod(); // INT  output
	e93196_delay_us(1000);	        
	e93196_hal_int_pin_low();      //PIR_INT  output low
	e93196_delay_us(1000);	         //1000us
	e93196_hal_int_pin_in_mod();  // INT  input 
	e93196_hal_int_pin_enable_int_mod();
}

/*******************************************************************************
 * @brief e93196_Doci_clock for read data use int pin
 *
 * @param none
 *
 * @return none
*******************************************************************************
static void e93196_Doci_clock(void)
{
  e93196_hal_int_pin_out_mod(); 		// INT  output 
  e93196_hal_int_pin_low();     		//PIR_INT  output low
  e93196_delay_us(10);          		// Wait a bit
  e93196_hal_int_pin_hight();   		// Set DOCI pin
  e93196_delay_us(1);		
  e93196_hal_int_pin_in_mod();  		// INT  input 
  e93196_delay_us(40);          		// Wait a bit
}

/*******************************************************************************
 * @brief e93196_read read the e93196 data
 *
 * @param none
 *
 * @return none
*******************************************************************************
static void e93196_read(void)
{
  uint8_t n;
  uint8_t b_out_range;
  uint16_t pir_voltage;
  uint8_t b_sensitivity;
  uint8_t b_blind_time;
  uint8_t b_pulse_count;
  uint8_t b_window_time;
  uint8_t b_motion_detect_en;
  uint8_t b_interrupt_source;
  uint8_t b_voltage_source;
  uint8_t b_regulator_en;
  uint8_t b_start_selftest;
  uint8_t b_sample_capacitor;
  uint8_t b_user_test_modes;
  

  e93196_hal_int_pin_disable_int_mod();
  // force read, at least 3 clocks of IC
  e93196_hal_int_pin_out_mod(); // INT  output 
  e93196_hal_int_pin_low();     // clear DOCI pin
  e93196_delay_us(100);
  e93196_hal_int_pin_hight();     // Set DOCI pin
  e93196_delay_us(1000);

  b_out_range=0;
  e93196_Doci_clock();
  if (e93196_GET_INT() == 1)
    b_out_range++;

  pir_voltage = 0;
  for (n = 0; n < 14; n++)   // There are 14 bits of data from the sensors
  {
    e93196_Doci_clock();
    pir_voltage<<=1;              // Make room
    if (e93196_GET_INT() == 1)
      pir_voltage++;
  }

    b_sensitivity=0;
    for(n=0;n<8;n++)   // There are 14 bits of data from the sensors
    {
      e93196_Doci_clock();
      b_sensitivity<<=1;              // Make room
      if (e93196_GET_INT() == 1)
        b_sensitivity++;
    }

    b_blind_time=0;
    for(n=0;n<4;n++)   // There are 14 bits of data from the sensors
    {
      e93196_Doci_clock();
      b_blind_time<<=1;              // Make room
      if (e93196_GET_INT() == 1)
        b_blind_time++;
    }

    b_pulse_count=0;
    for(n=0;n<2;n++)   // There are 14 bits of data from the sensors
    {
      e93196_Doci_clock();
      b_pulse_count<<=1;              // Make room
      if (e93196_GET_INT() == 1)
        b_pulse_count++;
    }

    b_window_time=0;
    for(n=0;n<2;n++)   // There are 14 bits of data from the sensors
    {
      e93196_Doci_clock();
      b_window_time<<=1;              // Make room
      if (e93196_GET_INT() == 1)
        b_window_time++;
    }

    b_motion_detect_en=0;
    e93196_Doci_clock();
    if (e93196_GET_INT() == 1)
      b_motion_detect_en++;

    b_interrupt_source=0;
    e93196_Doci_clock();
    if (e93196_GET_INT() == 1)
      b_interrupt_source++;

    b_voltage_source=0;
    for(n=0;n<2;n++)   // There are 14 bits of data from the sensors
    {
      e93196_Doci_clock();
      b_voltage_source<<=1;
      if (e93196_GET_INT() == 1)
        b_voltage_source++;
    }

    b_regulator_en=0;
    e93196_Doci_clock();
    if (e93196_GET_INT() == 1)
      b_regulator_en++;

    b_start_selftest=0;
    e93196_Doci_clock();
    if (e93196_GET_INT() == 1)
      b_start_selftest++;

    b_sample_capacitor=0;
    e93196_Doci_clock();
    if (e93196_GET_INT() == 1)
      b_sample_capacitor++;

    b_user_test_modes=0;
    for(n=0;n<2;n++)
    {
      e93196_Doci_clock();
      b_user_test_modes<<=1;              // Make room
      if (e93196_GET_INT() == 1)
        b_user_test_modes++;
    }
	
	e93196_hal_int_pin_low();	   // clear DOCI pin
	e93196_delay_us(1000);
	e93196_hal_int_pin_in_mod();  // INT  input 
	e93196_hal_int_pin_enable_int_mod();

}
*******************************************************************************/

/*******************************************************************************
 * @brief initial motion sensor
 *
 * @param none
 *
 * @return none
*******************************************************************************/
void (*e93196_int_callback)(uint8_t pin_level) = 0;
void e93196_init(void)
{
	e93196_int_callback = 0;
	e93196_hal_init();
	e93196_hal_serin_pin_out_mod();
	e93196_hal_int_pin_in_mod();  	// INT  input 
	e93196_hal_int_pin_enable_int_mod();
	e93196_delay_us(1000);	       		//1000us  
	//sensitivity , pulse_counter , motion_enable
	e93196_set_default();
	e93196_Clear_Interrupt_Pin();
}

void e93196_int_handler(void)
{
	uint8_t pin_level = 0;
	pin_level = e93196_hal_int_pin_level_get();
	if(pin_level == 1){
 		e93196_Clear_Interrupt_Pin();
		if(e93196_int_callback != 0){
			e93196_int_callback(pin_level);
		}
	}
}






